#include "romashka.h"
#include "RoQuery.h"
#include "RoStanzas.h"
#include "RoXmlStream.h"


RoQuery::RoQuery(RoAbstractComponent * parent):
    super(parent),
    dataAcceptor(parent),
    dataAcceptorMethod(ROMASHKA_QUERY_DATA_ACCEPTOR_SIGNATURE),
    resultAcceptor(parent),
    resultAcceptorMethod(ROMASHKA_QUERY_RESULT_ACCEPTOR_SIGNATURE)
{
}


inline bool checkSlotPresence(const QObject * obj, const char * method)
{
    return obj and obj->metaObject()->indexOfSlot(QMetaObject::normalizedSignature(method+1)) != -1;
}


inline bool checkMethodsCompatibility(const char * method1, const char * method2)
{
    return QMetaObject::checkConnectArgs( QMetaObject::normalizedSignature(method1),
                                          QMetaObject::normalizedSignature(method2) );
}


bool RoQuery::exec(QDomDocument argument)
{
    if ( not checkSlotPresence(resultAcceptor, resultAcceptorMethod) or
         not checkMethodsCompatibility(SIGNAL( query_result(bool,QDomDocument) ), resultAcceptorMethod) )
    {
        return false;
    }

    RoIqStanza requestStanza = RoIqStanza::createRequest(_remoteComponentName,
                                                         _remoteMethod,
                                                          argument );

    _rid = parentComponent()->sendStanza(requestStanza);
    if ( _rid.isNull() )
        return false;
    else
        emit requestSent(_rid);

    connect(this, SIGNAL( query_result(bool,QDomDocument) ),
            resultAcceptor, resultAcceptorMethod);

    if ( checkSlotPresence(dataAcceptor, dataAcceptorMethod) and
         checkMethodsCompatibility(SIGNAL( query_datum(QDomDocument) ), dataAcceptorMethod) )
    {
        connect(this, SIGNAL( query_datum(QDomDocument) ),
                dataAcceptor, dataAcceptorMethod);
    }

    return true;
}


void RoQuery::datum(RoIqStanza stanza)
{
    emit query_datum(stanza.payload());
}


void RoQuery::end(RoIqStanza stanza)
{
    emit query_result( stanza.type() == "error",
                       stanza.payload() );
}
